//******************************************************************************
//this code is protected by the GNU affero GPLv3
//author:Sylvain BERTRAND <sylvain.bertrand AT gmail dot com>
//                        <digital.ragnarok AT gmail dot com>
//******************************************************************************
#include "globals.h"

static void obj_release(struct client *c,s32 shm_pool_buffer_slot)
{
    c->objs[shm_pool_buffer_slot].state=CLIENT_OBJ_INVALID;
    client_obj_unref(c,c->objs[shm_pool_buffer_slot].buffer.shm_pool_slot);
}

s8 shm_pool_buffer_destroy(struct client *c,s32 shm_pool_buffer_slot)
{
  s32 n=client_obj_unref(c,shm_pool_buffer_slot);
  if(!n) c->objs[shm_pool_buffer_slot].state&=~CLIENT_OBJ_VISIBLE;
  return wl_display_ev_delete_id(c,c->objs[shm_pool_buffer_slot].id);
}

s8 shm_pool_buffer_new_visible(struct client *c,u32 shm_pool_buffer_id,
                    s32 shm_pool_slot,s32 offset,s32 w,s32 h,s32 stride,u32 fmt)
{
  s8 r=LWL_OK;
  s32 free_slot=CLIENT_FIRST_VALID_ID;
  while(1){
    if(free_slot==CLIENT_OBJS_MAX){
      r=LWL_ERR;
      break;
    }
    if(c->objs[free_slot].state&CLIENT_OBJ_INVALID){
      c->objs[free_slot].state=CLIENT_OBJ_BUFFER|CLIENT_OBJ_SHM_POOL_BUFFER
                                                            |CLIENT_OBJ_VISIBLE;
      c->objs[free_slot].release=obj_release;
      c->objs[free_slot].id=shm_pool_buffer_id;
      c->objs[free_slot].n=1;//the wire has a reference on it
      client_obj_ref(c,shm_pool_slot);
      c->objs[free_slot].buffer.shm_pool_slot=shm_pool_slot;
      //TODO:check the buffer fit in the pool 
      c->objs[free_slot].buffer.offset=offset;
      c->objs[free_slot].buffer.w=w;
      c->objs[free_slot].buffer.h=h;
      c->objs[free_slot].buffer.stride=stride;
      c->objs[free_slot].buffer.fmt=fmt;
      break;
    }
    ++free_slot;
  }
  return r;
}
